#pragma once

#include "vector3.h"
#include "matrix4x4.h"




namespace math
{
   template
   <
      typename float_t
   >
   class transformable
   {
   public:

      typedef float_t              float_t;
      typedef vector3<float_t>     vector3_t;
      typedef matrix3x3<float_t>   matrix3x3_t;
      typedef matrix4x4<float_t>   matrix4x4_t;

   private:

      /// Matrix that defines the transformable's local
      /// coordinate system, relative to the world's.
      matrix4x4_t   m_localToWorld;

   public:

      /**
       * Creates a transformable with an identity matrix.
       * The local coordinate system is the world's origin, using the
       * same scale and rotation.
       */
      transformable()
      {}

      /**
       * Create a transformable with the given local to world matrix.
       */
      transformable(const matrix4x4_t& localToWorld)
         : m_localToWorld(localToWorld)
      {}

      virtual ~transformable()
      {}



      /**
       * Get the local to world matrix.
       */
      matrix4x4_t localToWorld() const
      {
         return m_localToWorld;
      }

      /**
       * Get the center of the local coordinate system.
       */
      vector3_t position() const
      {
         return vector3_t(m_localToWorld._41, m_localToWorld._42, m_localToWorld._43);
      }

      /**
       * Get the rotation of the local coordinate system.
       */
      matrix3x3_t rotation() const
      {
         return m_localToWorld.rotation();
      }

      /**
       * Set the local to world matrix.
       */
      void setLocalToWorld(const matrix4x4_t& localToWorld)
      {
         m_localToWorld = localToWorld;
      }

      /**
       * Set the center of the local coordinate system.
       */
      void setPosition(const vector3_t& position)
      {
         m_localToWorld._41 = position.x;
         m_localToWorld._42 = position.y;
         m_localToWorld._43 = position.z;
      }
   };
}
///////////////////////////////////////////////////////////////////////////////////////////////////